package com.github.icloudpay.pay.core.service.pay.alipay.service;

import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import com.github.icloudpay.pay.core.feign.PayChannelConfigFeign;
import com.github.icloudpay.pay.core.inter.PayObjectService;
import com.github.icloudpay.pay.core.service.pay.LocalSignatureService;
import com.github.icloudpay.pay.core.service.pay.alipay.util.AliPayConfig;
import com.github.wxiaoqi.security.common.admin.pay.request.OnlinePaymentRequest;
import com.github.wxiaoqi.security.common.msg.ResponseCode;
import com.google.common.collect.Maps;


/**
 * 支付宝APP支付
 * @author 
 * 2018-6-6
 */
@Service("aliAppPaymentService")
public class AliAppPaymentService implements PayObjectService<OnlinePaymentRequest>{
	
	private static final Logger logger = LoggerFactory.getLogger(AliAppPaymentService.class);

    @Autowired
    private AliPayConfig aliPayConfig;
    @Autowired
    private LocalSignatureService localSignatureService;

    @Autowired
    private PayChannelConfigFeign payChannelConfigFeign;

    public Map<String, Object> pay(OnlinePaymentRequest request) {
    	
    	logger.info("****************调用支付宝APP支付接口开始*******************");
        
    	Map<String, Object> responseMap = new HashMap<String, Object>();
		
    	Map<String, Object> reqMap = new HashMap<String, Object>();
    	reqMap.put("platformId", request.getPlatformId());
    	reqMap.put("merchantId", request.getMerchantId());
    	reqMap.put("payChannelNo", request.getPayChannelNo());
		Map<String, Object> respMap = payChannelConfigFeign.query(reqMap);
        if(!(boolean) respMap.get("success")){
            responseMap.put("success", false);
			responseMap.put("code", ResponseCode.PAYCHANNEL_CONFIGURATION_NOTEXIST.getCode());
			responseMap.put("msg", ResponseCode.PAYCHANNEL_CONFIGURATION_NOTEXIST.getMessage());
			return responseMap;
        }
        @SuppressWarnings("unchecked")
		Map<String, Object> configMap = (Map<String, Object>)respMap.get("payChannelConfigInfo");
        
        String notifyUrl = aliPayConfig.getBackCallbackUrl() + "/callBack/aliPay";
        
        String orderInfo = getOrderInfo(aliPayConfig, configMap, request, notifyUrl);
        
        String sign = sign(orderInfo,configMap);
        
        try {
            // 仅需对sign 做URL编码
            sign = URLEncoder.encode(sign, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }

        // 完整的符合支付宝参数规范的订单信息
        final String payInfo = orderInfo + "&sign=\"" + sign;
        
        Map<String,Object> response = Maps.newHashMap();
        Map<String,Object> payInfoMap = new HashMap<String, Object>();
        payInfoMap.put("payInfo", payInfo);
        response.put("payInfo", payInfoMap);
        response.put("success", true);
        response.put("code", ResponseCode.OK.getCode());
        response.put("msg", ResponseCode.OK.getMessage());
        return response;
    }
    
    private String getOrderInfo(AliPayConfig aliPayConfig, Map<String, Object> configMap, OnlinePaymentRequest request,String notifyUrl){
        // 签约合作者身份ID
        String orderInfo = "app_id=" + configMap.get("outMerNo");

        // 签约卖家支付宝账号
        orderInfo += "&method=" + "alipay.trade.app.pay";
        
        //编码格式
        orderInfo += "&charset=" + "utf-8";
        
        //签名算法类型
        orderInfo += "&sign_type=" + "RSA2";
        
        //请求时间
        Date currentTime = new Date();
        SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        String dateString = formatter.format(currentTime);
        orderInfo += "&timestamp=" + dateString;
        
        //回调地址
        orderInfo += "&notify_url=" + aliPayConfig.getBackCallbackUrl() + "/callBack/aliPay";
        
        //请求参数集合
        orderInfo += "&biz_content=" + "{";
        
        if(request.getProductName() == null){
            // 商品详情
            orderInfo += "," + "\"body\":" + "\"" + "N/A" + "\"";
        }else{
            // 商品详情
            orderInfo += "," + "\"body\":" + "\"" + request.getProductName() + "\"";
        }
        
     // 商品名称
        if(StringUtils.hasText(request.getProductName())){
            orderInfo += "," + "\"subject\":" + "\"" + request.getProductName() + "\"";
        }else{
            orderInfo += "," + "\"subject\":" + "\"" + "N/A" + "\"";
        }

        // 商户网站唯一订单号
        orderInfo += "," + "\"out_trade_no\":" + "\"" + request.getSerialNo() + "\"";

        // 商品金额
        orderInfo += "," + "\"total_amount\":" + "\"" + request.getOrderAmt().toString() + "\"";

        // 产品码
        orderInfo += "," + "\"product_code\":" + "\"" + "QUICK_MSECURITY_PAY" + "\"";

        // 设置未付款交易的超时时间
        // 默认30分钟，一旦超时，该笔交易就会自动被关闭。
        // 取值范围：1m～15d。
        // m-分钟，h-小时，d-天，1c-当天（无论交易何时创建，都在0点关闭）。
        // 该参数数值不接受小数点，如1.5h，可转换为90m。
        orderInfo += "," + "\"timeout_express\":" + "\"" + "30m" + "\"" + "}";

        return orderInfo;
    }
    
    private String sign(String content,Map<String, Object> configMap) {
        return localSignatureService.sign(content, configMap);
    } 

}
